
import os
import sys
import wx
from sqloper import *
from pathutil import *
import ConfigParser
import string
import logging
import shutil



logging.basicConfig(level=logging.DEBUG, filename='xbfm.log',
                    format='%(asctime)s %(levelname)s: %(message)s',
                    datefmt='%Y-%m-%d %H:%M:%S')

#clogger = logging.getLogger("console_Log")

#ch = logging.StreamHandler()
#ch.setLevel(logging.DEBUG)
#format='%(asctime)s %(levelname)s: %(message)s',
#datefmt='%Y-%m-%d %H:%M:%S'
#ch.args=(sys.stdout,format)

#clogger.addHandler(ch)




class RedirectText(object):
    def __init__(self,aWxTextCtrl):
        self.out=aWxTextCtrl

    def write(self,string):
        self.out.WriteText(string)
       
    

class LogWin(wx.Dialog,wx.ListCtrl):

    def __init__(self,MoveList):
        wx.Dialog.__init__(self, None, wx.ID_ANY, "XBFM File Operations")

        
        panel = wx.Panel(self, wx.ID_ANY,size=wx.Size(800, 600))
        self.SetClientSize(wx.Size(800,600))
        self.logwin = wx.TextCtrl(panel, wx.ID_ANY, size=(800,500),
                          style = wx.TE_MULTILINE|wx.TE_READONLY|wx.HSCROLL)
        self.logwin.SetBackgroundColour(wx.Colour(0, 0, 0))
        self.logwin.SetForegroundColour(wx.Colour(255, 255, 255))
              
        self.MoveList = MoveList
        self.btn = wx.Button(id=wx.NewId(), label='Start',
              name='', parent=panel, pos=wx.Point(400, 550),
              size=wx.Size(-1, -1), style=0)
        self.Bind(wx.EVT_BUTTON, self.onButton, self.btn)

        # Add widgets to a sizer
        sizer = wx.BoxSizer(wx.VERTICAL)
        sizer.Add(self.logwin, 1, wx.ALL|wx.EXPAND, 5)
        sizer.Add(self.btn, 0, wx.ALL|wx.CENTER, 5)
        panel.SetSizer(sizer)

        # redirect text here
        redir=RedirectText(self.logwin)
        sys.stdout=redir
        sys.stderr = redir 
        
        #Item2Move = self.MoveList.GetItem(i,0).GetText()

    def onButton(self, event):
        Total_Items = self.MoveList.GetItemCount()
        if Total_Items == 0:
            self.Close()
        if Total_Items != 0:
            Seperator = os.sep
            while Total_Items > 0:
                Total_Items = self.MoveList.GetItemCount()
                if Total_Items == 0:
                    return
                i = Total_Items -1
            #Move Each Item
                #TODO  BUG Creating extra folder - if move object is a folder
                # then one level needs to be removed
                CPF = "OFF"
                SourceDir = self.MoveList.GetItem(i,0).GetText()
                DestDir = self.MoveList.GetItem(i,1).GetText()
                CPF = self.MoveList.GetItem(i,2).GetText()
                
                #self.LogWin.Clear()
                print "Starting File/Folder Moves"
                File = ''
                if os.path.isfile(SourceDir):
                    File = os.path.basename(SourceDir)
                    DestFolder = DestDir.replace(File,'',1)
                    SourceFolder = SourceDir.replace(File,'',1)
                    print "Moving File %s" %File

                #If destination is folder we need to remove
                #the last folder name from DestFolder
                if os.path.isdir(SourceDir):
                    DestFolder = DestDir
                    SourceFolder = SourceDir
                    if os.path.exists(DestDir):

                        # If final folder in source and dest are the same
                        # move function will fail - if dest empty remove
                        # and let shutil recreate it. If dest is not l
                        # empty we wil have to abort
                        if os.path.basename(SourceDir) == os.path.basename(DestDir):
                            templist = []
                            templist = os.listdir(DestFolder)
                            #If destination folder empty remove it
                            #as it will be recreated on move
                            if templist == []:
                                os.rmdir(DestFolder)
                                DestFolder = DestDir.replace(os.path.basename(DestDir),'',1)
                                logging.debug(u"Duplicate folder name removed in %s" % DestFolder)
                            else:
                                wx.MessageBox("Destination folder is not empty!  Remove from queue and add subfolders")
                                
                                return

# See how large the file path is and check for room in destination
 # to copy files. # pathbytes = os.path.getsize(SourceFolder)

 # Start out false and change to true if all conditions are me
                try:
                    testDir = SourceFolder
                except:
                    wx.MessageBox("Source folder no longer exists-Are you rerunning move?")
                    return
                AllOK = False
                # Check to see if original source is listed in path table
                if not testDir.endswith(Seperator):
                    testDir = testDir + Seperator
                # test Dir is SourceFolder
                Source_ID = getPathID(testDir)
                SourceID = str(Source_ID)
                #print DestID
                if SourceID != 'None':
                    #TODO Get the number of orignal records and match
                    #with number after moves are complete.
                    #oldRecCount = testFilePath(DestID)
                    SourceCT = getContentType(testDir)
                    print "Original Video Folder Record Found: %s" %SourceID

                    #print SourceCT
                    AllOK = True
                    logging.debug(u"All OK is True set by SourceID")
                    print "All OK is True - Starting Move"               
                    # See if new path record has been added to XBMC already
                # If not the user can add it now. If User chooses
                # No then the process does not complete.
                testDir =  DestFolder
                if not testDir.endswith(Seperator):
                    testDir = testDir + Seperator
                Dest_ID = getPathID(testDir)
                DestID = str(Dest_ID)
                if DestID == 'None':

                   
                    logging.debug(u"Creating new Path record")
                    print "Creating new path record"
                    # Try again to get the path ID
                    AllOK = False
                    # Get each folder from bottom to top
                    addPath(testDir,'','')
                    Dest_ID = getPathID(testDir)
                    DestID = str(Dest_ID)
                    if DestID != 'None':
                        AllOK = True
                        
                        logging.debug(u"Creation of New Path Record Suceeded")
                        print "Creation of new path record succeeded"
# Get the content type from the old folder from parent folder - Could be
# on any level so you have to search backwards from the folder being moved
# because there could be different types on same drive.
                        RootFolder = getRootFolder(DestFolder)

            # TODO sqloper.py See one of the new paths has
            # a content type the same as the old one.  If yes
            # we should be done.  If not we need to create one.

            #Found needed records so start the move
                AllOK = True

                if Dest_ID == 'None':
                    AllOK = False
                    wx.MessageBox("Missing Record in DB - Move Cancelled!")
                    return
                if Source_ID == 'None':
                    AllOK = False
                    wx.MessageBox("Missing Record in DB - Move Cancelled!")
                    return
                if AllOK:
                    dstName = os.path.join(DestFolder, os.path.basename(SourceDir))
                    logging.debug(u"Move From: %s" %SourceDir)
                    logging.debug(u"Move To: %s" %DestFolder)
                    print "Moving:  %s" %SourceDir                    
                    wx.SafeYield(None,True)
                    SrcSize = 0
                    DestSize = 0
                    if os.path.isdir(SourceDir):
                        SrcSize = getDirectorySize(SourceDir)
                        try:shutil.move(SourceDir,DestFolder)
                        except IOError, er:
                            logging.debug(u"Unable to move folder: %s" % er)
                            try:shutil.copytree(SourceDir, DestFolder, symlinks=True)
                            except IOError, er:
                                logging.debug(u"Unable to move file: %s" % er)
                                self.LogWin.Show(False)
                                wx.MessageBox("Error Moving Files - Check Log")
                                return
                        if CPF == "ON":
                            DestSize = getDirectorySize(DestFolder)
                        else:
                            DestSize = getDirectorySize(dstName)
                        if DestSize != SrcSize:
                            print "Size of Destination not same as Source"
                    else:
                        try: shutil.move(SourceDir,DestDir)
                        except IOError, er:
                            logging.debug(u"Unable to move file: %s" % er)
                            
                            wx.MessageBox("Unable to move file: %s" % er)
                            return
                    #print "Source Dir: %s" %SourceDir
                    logging.debug(u"Moved Source: %s" % SourceDir)
                    print "Moved: %s" % SourceDir                  
                    logging.debug(u"To Dest: %s" % DestDir)
                    print "To Dest: %s" % DestDir
                    logging.debug(u"Source Size: %s" % SrcSize +"   Dest Size: %s" % DestSize)
                    print "Source Size: %s" % SrcSize +"   Dest Size: %s" % DestSize 
                    testDir = SourceFolder

    # Before changing all the path file records we need to get
    # all the thumbnails for the files and rename them to the crc
    # of the new path. Best way is to do it from the sqloper.py so
    # as each path is changed we can rename the thumb files. Logic
    # dictates that it should only be changed if the db record was
    # updated correctly.  Likewise the old thumb is deleted after the
    # new thumb is copied and verified.  These operations could be done
    # quicker with a rename but this way is safer and easier to debug.

                    # Change path on records
                    # Originally changed pathID in files table - changed to
                    # update path on path records so that we don't loose
                    # relationships in other tables. 
                    #logging.debug(u"Setting Dest Path ID to: %s" % Dest_ID +" From: %s" % Source_ID)
                    if os.path.isfile(DestDir+os.sep+File):
                        File = os.path.basename(SourceDir)
                        retcode = setFilePath(Source_ID,Dest_ID,File)
                    else:
                        retcode = setAllPaths(SourceDir,DestDir)
                    if retcode == 0:
                        
                        #wx.MessageBox(u"Error setting new Path record - Review Log")
                        logging.debug(u"Path ID changed on %s" % retcode + " records")
                        logging.debug(u"May need to move %s" %DestDir +" back to source")
                    wx.SafeYield(None,True)
                    self.MoveList.Select(i)
                    self.MoveList.DeleteItem(i)
                    i-1
                    Total_Items = self.MoveList.GetItemCount()
                    if Total_Items == 0:
                        print "All moves completed...I think"
                        self.btn.SetLabel("Close")
                        #TODO Check database and files to ensure changes were made properly
                       


